import React, { useEffect, useRef, useState } from 'react';
import {
  Animated,
  Easing,
  Pressable,
  SafeAreaView,
  Text,
  Slider,
  View,
  Switch
} from 'react-native';

function App(): JSX.Element {
  const [isCircle, setIsCircle] = useState(false)

  const animationState = {
    start: 0,
    end: 100
  }

  const [duration, setDuration] = useState(1)
  const [useNativeDriver, setUseNativeDriver] = useState(true)

  const animationValue = useRef(new Animated.Value(isCircle ? animationState.end : animationState.start)).current
  const animationNativeValue = useRef(new Animated.Value(isCircle ? animationState.end : animationState.start)).current

  const inputRange = [animationState.start, animationState.end]
  const scaleValue = (useNativeDriver ? animationNativeValue : animationValue).interpolate({ inputRange: inputRange, outputRange: [2, 0.4] })
  const translateValue = (useNativeDriver ? animationNativeValue : animationValue).interpolate({ inputRange: inputRange, outputRange: [100, 0] })

  useEffect(() => { 
    animationValue.setValue(isCircle ? animationState.end : animationState.start)
    animationNativeValue.setValue(isCircle ? animationState.end : animationState.start)
  }, [useNativeDriver])

  return (
    <SafeAreaView style={{ flexDirection: 'column', justifyContent: 'space-between' }}>
      <View style={{ justifyContent: 'center', paddingHorizontal: 16, paddingVertical: 12 }}>
        <Text>Duration: {duration.toFixed(2)}</Text>
        <Slider
          style={{ width: '100%' }}
          minimumValue={0.2}
          maximumValue={5}
          value={duration}
          onValueChange={setDuration} />
      </View>
      <View style={{ height: 1, backgroundColor: 'black', opacity: 0.1 }} />
      <View style={{ justifyContent: 'space-between', flexDirection: 'row', paddingHorizontal: 16, paddingVertical: 12 }}>
        <Text style={{ textAlignVertical: 'center', marginEnd: 8 }}>Use Native Driver</Text>
        <Switch value={useNativeDriver} onValueChange={setUseNativeDriver} />
      </View>
      <View style={{ height: 1, backgroundColor: 'black', opacity: 0.1 }} />
      <Pressable style={{ height: '100%' }} onPress={() => {
        setIsCircle(!isCircle)
        Animated.timing(useNativeDriver ? animationNativeValue : animationValue,
          {
            toValue: isCircle ? animationState.start : animationState.end,
            useNativeDriver: useNativeDriver,
            duration: duration * 1000,
            easing: Easing.elastic(1)
          })
          .start()
      }}>
        <Animated.View style={{
          width: '50%',
          aspectRatio: 1,
          alignSelf: 'center',
          justifyContent: 'center',
          backgroundColor: 'purple',
          borderRadius: useNativeDriver ? animationNativeValue : animationValue,
          transform: [
            { scale: scaleValue },
            { translateY: translateValue }
          ]
        }}>
          <Text style={{ alignSelf: 'center', fontSize: 28, fontWeight: 'bold', color: 'white' }}>Press Here</Text>
        </Animated.View>
      </Pressable>
    </SafeAreaView>
  );
}

export default App;
